﻿using Android.Content;
using Android.Provider;
using Microsoft.Extensions.Logging;
using NLog.Extensions.Logging;
using OpenAiMobile.Database;
using OpenAiMobile.Models;
using OpenAiMobile.Repositories;
using OpenAiMobile.Services;
using OpenAiMobile.Util.Services;

namespace OpenAiMobile;

public static class MauiProgram
{
    public static MauiApp CreateMauiApp()
    {
        var builder = MauiApp.CreateBuilder();

        // Add NLog for Logging
        builder.Logging.ClearProviders();
        builder.Logging.AddNLog();

        builder
            .UseMauiApp<App>()
            .ConfigureFonts(fonts =>
            {
                fonts.AddFont("OpenSans-Regular.ttf", "OpenSansRegular");
                fonts.AddFont("OpenSans-Semibold.ttf", "OpenSansSemibold");
            })
            .UsePrism(prism =>
            {
                prism.RegisterTypes(container =>
                {
                    container.Register<IHttpService, HttpService>();
                    container.RegisterSingleton<ILogService, LogService>();
                    container.RegisterSingleton<IConfigService, ConfigService>();
                    container.RegisterSingleton<ISessionService, SessionService>();
                    container.RegisterSingleton<IPlatformService, PlatformService>();
                    container.RegisterSingleton<IStatisticsService, StatisticsService>();
                    container.RegisterSingleton<ISqliteService, SqliteService>();

                    //注入数据仓库
                    container.Register<SqliteDbContext>();
                    container.Register<IRepository<ConfigModel>, ConfigRepository>();
                });
                prism.OnInitialized(container =>
                {
                    //启动日志服务
                    var logService = container?.Resolve<ILogService>();
                    logService?.Startup();

                    //准备SQLite数据库
                    // ReSharper disable once IdentifierTypo
                    var sqliteService = container?.Resolve<ISqliteService>();
                    sqliteService?.PrepareSqliteAsync().GetAwaiter().GetResult();

                    //CheckPermissions().GetAwaiter().GetResult();

                    //EF Core预热
                    WarmupDatabase(container);

                    //加载配置(基于SQLite)
                    var configService = container.Resolve<IConfigService>();
                    configService?.LoadConfigAsync().GetAwaiter().GetResult();

                    // Do some initializations here
                    var sessionService = container.Resolve<ISessionService>();
                    MyServiceExtension.SessionService = sessionService;

                    var statisticsService = container.Resolve<IStatisticsService>();
                    statisticsService?.Startup();
                });
            });

        return builder.Build();
    }

    private static async Task CheckPermissions()
    {
        //写权限
        var status = await Permissions.CheckStatusAsync<Permissions.StorageWrite>();
        if (status != PermissionStatus.Granted)
        {
            status = await Permissions.RequestAsync<Permissions.StorageWrite>(); //弹窗求授权
        }

        if (status != PermissionStatus.Granted)
        {
            var mainPage = Application.Current?.MainPage;
            if (mainPage != null)
            {
                await mainPage.DisplayAlert(
                    "错误：",
                    "必须给予存储访问权限！请手动给予权限后再重新登录！",
                    "跳转到手动设置页面"
                    );
            }

#if ANDROID
            Intent intent = new Intent(Settings.ActionApplicationDetailsSettings);
            Android.Net.Uri uri = Android.Net.Uri.FromParts("package", AppInfo.Current.PackageName, null);
            intent.SetData(uri);
            Android.App.Application.Context.StartActivity(intent);
#endif
        }
    }

    private static void WarmupDatabase(IContainerProvider container)
    {
        using var dbContext = container?.Resolve<SqliteDbContext>();

        // this is for demo purposes only, to make it easier
        // to get up and running
        dbContext?.Database.EnsureCreated();

        // load the entities into EF Core
        dbContext?.LoadEntities();

        // ReSharper disable once AssignmentIsFullyDiscarded
        //_ = dbContext.Model; //force the model creation
    }
}
